package de.mmis.core.infrastructure.gui;

import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.text.DateFormat;
import java.util.ArrayList;
import java.util.Date;

import javax.swing.Timer;
import javax.swing.table.AbstractTableModel;

import de.mmis.core.base.Pair;
import de.mmis.core.base.event.Observable;
import de.mmis.core.base.event.Observer;
import de.mmis.core.base.infrastructure.InfrastructureEvent;
import de.mmis.core.base.infrastructure.InfrastructureEvent.InfrastructureEventType;

class HeartbeatTableModel extends AbstractTableModel implements
		Observer<InfrastructureEvent> {

	private static final long serialVersionUID = 4918740268728792699L;

	private static String[] columnNames = new String[] { "Host",
			"Last Heartbeat Time", "Last Heartbeat (seconds)" };

	private ArrayList<Pair<String, Date>> data = new ArrayList<Pair<String, Date>>();

	public HeartbeatTableModel() {
		new Timer(1000 * 5, new ActionListener() {
			@Override
			public void actionPerformed(ActionEvent e) {
				fireTableDataChanged();
			}
		}).start();
	}

	@Override
	public String getColumnName(int column) {
		if (column < 0 || column >= columnNames.length)
			return "";

		return columnNames[column];
	}

	@Override
	public int getRowCount() {
		return data.size();
	}

	@Override
	public int getColumnCount() {
		return columnNames.length;
	}

	@Override
	public Object getValueAt(int rowIndex, int columnIndex) {
		Pair<String, Date> pair = data.get(rowIndex);

		switch (columnIndex) {
		case 0:
			return pair.getFirst();
		case 1:
			return DateFormat.getDateTimeInstance().format(pair.getSecond());
		case 2:
			long now = System.currentTimeMillis();
			long diff = now - pair.getSecond().getTime();
			return new Long(diff / (1000));
		default:
			return null;
		}
	}

	@Override
	public void notify(Observable<? extends InfrastructureEvent> sender,
			InfrastructureEvent event) {
		if (event.getEventType() != InfrastructureEventType.HEARTBEAT)
			return;

		String host = event.getAddressS();
		Date time = new Date();

		Pair<String, Date> pair = null;
		for (Pair<String, Date> p : data)
			if (p.getFirst().equals(host)) {
				pair = p;
				break;
			}

		if (pair == null) {
			pair = new Pair<String, Date>(host, time);
			data.add(pair);
		} else
			pair.setSecond(time);

		fireTableDataChanged();
	}
}
